package com.xm.thread;

import com.xm.thread.bean.MyRunable;
import lombok.extern.slf4j.Slf4j;

import java.util.concurrent.*;

@Slf4j
public class ExecutorService02 {
    public static void main(String[] args) {
        basic();
        execute();
        completableFuture();
        scheduled();
    }

    /**
     * 基础线程创建
     */
    public static void basic() {
        try {
            new Thread(new MyRunable()).start();

            //实现 Callable 获取返回值
            FutureTask<Integer> futureTask = new FutureTask<>(() -> {
                return 42;
            });
            new Thread(futureTask).start();
            Integer rev = futureTask.get();
            log.info("FutureTask rev = {}", rev);
        } catch (InterruptedException | ExecutionException e) {
            throw new RuntimeException(e);
        } finally {
        }
    }

    /**
     * 线程池执行任务
     */
    public static void execute() {
        try {
            ExecutorService executor = Executors.newFixedThreadPool(4);
            executor.execute(() -> {
                log.info("异步任务逻辑");
            });

            //提交 Callable 任务
            Future<Integer> future = executor.submit(() -> {
                return 123;
            });

            Integer rev = future.get();
            log.info("Future rev = {}", rev);
            executor.shutdown();
        } catch (InterruptedException | ExecutionException e) {
            throw new RuntimeException(e);
        } finally {
        }
    }

    /**
     * CompletableFuture（Java 8+）
     */
    public static void completableFuture() {
        CompletableFuture.supplyAsync(() -> "hello")
                .thenApplyAsync(s -> s + " world")
                .thenAccept(log::info);
    }

    /**
     * 定时任务调度
     */
    public static void scheduled() {
        try {
            ScheduledExecutorService executor = Executors.newScheduledThreadPool(2);
            executor.scheduleAtFixedRate(new MyRunable(), 0, 1, TimeUnit.SECONDS);

            Thread.sleep(3000L);
            executor.shutdown();
        } catch (InterruptedException e) {
            throw new RuntimeException(e);
        } finally {
        }
    }
}
